/*
 * Copyright (C) 2011 flashflexpro@gmail.com  All Rights Reserved.  No
 *   use, copying or distribution of this work may be made except in
 *   accordance with a valid license agreement from flashflexpro@gmail.com
 *   This notice must be included on all copies, modifications and
 *   derivatives of this work.
 *
 *   flashflexpro@gmail.com MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT
 *   THE SUITABILITY OF THE SOFTWARE, EITHER EXPRESS OR IMPLIED,
 *   INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
 *   MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, OR
 *   NON-INFRINGEMENT. flashflexpro@gmail.com SHALL NOT BE LIABLE FOR ANY DAMAGES SUFFERED
 *   BY LICENSEE AS A RESULT OF USING, MODIFYING OR DISTRIBUTING THIS
 *   SOFTWARE OR ITS DERIVATIVES.
 */

/**
 * @author flashflexpro@gmail.com
 * Date: 11-1-18
 * Time: ����7:19
 */
package com.flashflexpro.as3lib {
import flash.events.Event;
import flash.events.IEventDispatcher;

import mx.core.MXMLObjectAdapter;

[Bindable]
public class ChainEndWatcher extends MXMLObjectAdapter {
    public function ChainEndWatcher() {
    }

    private var _eventDispatcher:IEventDispatcher;
    [Bindable( event="dispatcherChanged")]
    public function get eventDispatcher():Object {
        return _eventDispatcher;
    }

    public function set eventDispatcher(value:Object):void {
        if (_eventDispatcher != value) {
            tryRemoveEventListener();

            if( value is IEventDispatcher ){
                _eventDispatcher = value as IEventDispatcher;
                dispatchEvent(new Event("dispatcherChanged"));
                tryAddEventListener();
            }
        }
    }

    public var eventHandler:Function;

    private var _destroyed:Boolean = false;
    public function destroy():void {
        tryRemoveEventListener();
        _destroyed = true;
        _eventDispatcher = null;
        _eventType = null;
        eventHandler = null;
    }

    private var _enabled:Boolean=true;
    
    [Bindable(event="enableChanged")]
    public function get enabled():Boolean {
        return _enabled;
    }

    public function set enabled(value:Boolean):void {
          if( value != _enabled ){
            _enabled= value;
            dispatchEvent( new Event( "enableChanged" ) );
          }
    }

    public var trigerOnReady:Boolean = true;

    private var _eventType:String;

    [Bindable(event="eventTypeChanged")]
    public function get eventType():String {
        return _eventType;
    }

    public function set eventType(value:String):void {
        if (value != _eventType) {
            tryRemoveEventListener();
            if( value != null ){
                _eventType = value;
                dispatchEvent(new Event("eventTypeChanged"));
                tryAddEventListener();
            }
        }
    }

    private function eventHandleDelegate( ev:Event = null):void{
        if( _eventDispatcher == null || eventHandler == null ){
            CONFIG::debugging{
                trace( this + ".eventHandleDelegate, oh this can happend really?!");
            }
            return;
        }
        if( enabled ){
            eventHandler.apply( null, [ ev ] );
        }
    }

    private function tryAddEventListener():void {
        if (_eventDispatcher != null && eventType != null ) {
            _eventDispatcher.addEventListener(eventType, eventHandleDelegate);
            if (trigerOnReady ) {
                eventHandleDelegate();
            }
        }
    }

    private function tryRemoveEventListener():void {
        if (_eventDispatcher != null && eventType != null ) {
            _eventDispatcher.removeEventListener(eventType, eventHandleDelegate);
        }
    }


}
}